/**
 * Copyright 2010, Lars J. Nilsson <http://www.larsan.net> 
 * 
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

package net.larsan.dconf.prefs;

import java.util.List;
import java.util.Properties;
import java.util.prefs.AbstractPreferences;
import java.util.prefs.BackingStoreException;

import net.larsan.dconf.DNode;
import net.larsan.dconf.PropertiesHandler;

/**
 * This is the preferences implementation of the node store. It 
 * can be created manually using available nodes, but is usually 
 * fetched form the system preferences object.
 * 
 * <p>For the moment, this object does not give any guarantees about
 * flushing or transactions, this will be up to the actual node store
 * Implementations to handle.</p>
 * 
 * @author Lars J. Nilsson
 */
public class DNodePreferences extends AbstractPreferences implements PropertiesHandler {

	private final DNode node;
	
	/**
	 * @param node Node to create preferences from, must not be null
	 */
	public DNodePreferences(DNode node) {
		this((node.getParent() == null ? null : new DNodePreferences(node.getParent())), node);
	}

	/**
	 * @param parent Parent node, may be null
	 * @param node Node to create preferences from, must not be null
	 */
	public DNodePreferences(DNodePreferences parent, DNode node) {
		super(parent, node.getPath().getName());
		this.node = node;
	}
	
	@Override
	public Properties exportAsProperties() {
		return node.exportAsProperties();
	}
	
	@Override
	public void importProperties(Properties p) {
		node.importProperties(p);
	};
	
	public DNode getInternalNode() {
		return node;
	}

	@Override
	protected AbstractPreferences childSpi(String name) {
		return new DNodePreferences(this, node.getChild(name, true));
	}

	@Override
	protected String[] childrenNamesSpi() throws BackingStoreException {
		List<DNode> list = node.getChildren();
		String[] arr = new String[list.size()];
		for (int i = 0; i < list.size(); i++) {
			arr[i] = list.get(i).getPath().getName();
		}
		return arr;
	}

	@Override
	protected void flushSpi() throws BackingStoreException { }

	@Override
	protected String getSpi(String key) {
		return node.getAttributes().get(key);
	}

	@Override
	protected String[] keysSpi() throws BackingStoreException {
		return node.getAttributes().keySet().toArray(new String[node.getAttributes().keySet().size()]);
	}

	@Override
	protected void putSpi(String key, String value) {
		node.setAttribute(key, value);
	}

	@Override
	protected void removeNodeSpi() throws BackingStoreException {
		node.remove();
	}

	@Override
	protected void removeSpi(String key) {
		node.removeAttribute(key);
	}

	@Override
	protected void syncSpi() throws BackingStoreException { }
	
}
